// #include <iostream>
// #include <cstdio>
// #include <signal.h>
// #include <sys/types.h>
// #include <sys/wait.h>

// #include <unistd.h>

// void Count(int cnt)
// {
//     while (cnt)
//     {
//         printf("cnt: %2d\r", cnt);
//         fflush(stdout);
//         cnt--;
//         sleep(1);
//     }
//     printf("\n");
// }

// void handler(int signo)
// {
//     std::cout << "get a signo: " << signo << "正在处理中..." << std::endl;
//     Count(20);
// }

// int main()
// {
//     struct sigaction act, oact;
//     act.sa_handler = handler;
//     act.sa_flags = 0;
//     sigemptyset(&act.sa_mask);
//     sigaddset(&act.sa_mask, 3);
//     sigaction(SIGINT, &act, &oact);
//     while (true)
//     {
//         sleep(1);
//     }

//     return 0;
// }

#include <iostream>
#include <signal.h>
#include <unistd.h>

void handler(int signo)
{
    std::cout << "get a signo: " << signo << "正在处理中..." << std::endl;
}

int main()
{
    struct sigaction act, oact;
    act.sa_handler = handler;
    act.sa_flags = 0;
    sigemptyset(&act.sa_mask); //?
    sigaction(SIGINT, &act, &oact);
    while (true)
    {
        sleep(1);
    }

    return 0;
}




// void handler(int signo)
// {
//     // 1.我有非常多的子进程，在同一时刻退出了
//     // 2.我有非常多的子进程，在同一时刻只有一部分退出了
//     while (1)
//     {
//         pid_t ret = waitpid(-1, NULL, WNOHANG);
//         if (ret == 0)
//         {
//             break;
//         }
//     }
//     //printf("pid: %d,%d 号信号，正在被捕捉！\n", getpid(), signo);
// }

// void Count(int cnt)
// {
//     while (cnt)
//     {
//         printf("cnt: %2d\r", cnt);
//         fflush(stdout);
//         cnt--;
//         sleep(1);
//     }
//     printf("\n");
// }

// void handler(int signo)
// {
//     pid_t ret;
//     while ((ret = waitpid(-1, NULL, WNOHANG)) > 0) {
//         // 成功回收一个子进程
//         // 可以在这里添加更多的处理逻辑，如记录日志等
//     }
//     if (ret == -1 && errno != ECHILD) {
//         // 处理 waitpid 错误，除了没有子进程可回收的情况
//         perror("waitpid");
//     }
// }

// int main()
// {

//     signal(SIGCHLD, handler);
//     printf("我是父进程，%d,ppid：%d，我要退出啦\n", getpid(), getppid());

//     pid_t id = fork();
//     if (id == 0)
//     {
//         printf("我是子进程，%d,ppid：%d，我要退出啦\n", getpid(), getppid());
//         Count(5);
//         exit(1);
//     }
//     while (1)
//         sleep(1);
//     return 0;
// }

// #include <stdio.h>
// #include <stdlib.h>
// #include <signal.h>
// #include <sys/types.h>
// #include <sys/wait.h>
// #include <unistd.h>
// #include <errno.h>

// // 倒计时函数
// void Count(int cnt)
// {
//     while (cnt)
//     {
//         printf("cnt: %2d\r", cnt);
//         fflush(stdout);
//         cnt--;
//         sleep(1);
//     }
//     printf("\n");
// }

// SIGCHLD 信号处理函数
// void handler(int signo)
// {
//     //1.我有非常多的子进程，在同一时刻退出了
//     // 2.我有非常多的子进程，在同一时刻只有一部分退出了。
//     pid_t ret;
//     printf("SIGCHLD 信号被捕获，开始回收子进程\n");
//     while ((ret = waitpid(-1, NULL, WNOHANG)) > 0)
//     {
//         printf("成功回收子进程，进程 ID: %d\n", (int)ret);
//     }
//     if (ret == -1 && errno != ECHILD) // 处理 waitpid 错误，除了没有子进程可回收的情况
//     {
//         perror("waitpid");
//     }
// }

//循环回收：使用 while 循环和 waitpid(-1, NULL, WNOHANG) 不断尝试回收已退出的子进程。-1 表示等待任意子进程，WNOHANG 选项使 waitpid 函数非阻塞，如果没有子进程退出则立即返回 0。
//只要 waitpid 返回值大于 0，就意味着成功回收了一个子进程，会继续循环尝试回收其他已退出的子进程。
//错误处理：当 waitpid 返回 -1 且 errno 不等于 ECHILD（表示没有子进程可回收）时，说明出现了其他错误，使用 perror 输出错误信息。


// int main()
// {
//     struct sigaction act;
//     act.sa_handler = SIG_IGN;
//     sigemptyset(&act.sa_mask);
//     act.sa_flags = 0;

//     // 使用 sigaction 注册信号处理函数
//     if (sigaction(SIGCHLD, &act, NULL) == -1)
//     {
//         perror("sigaction");
//         return 1;
//     }

//     printf("我是父进程，%d，ppid：%d，正在等待子进程退出...\n", getpid(), getppid());

//     pid_t id = fork();
//     if (id == 0)
//     {
//         // 子进程
//         printf("我是子进程，%d，ppid：%d，我要开始倒计时并退出啦\n", getpid(), getppid());
//         Count(5);
//         exit(1);
//     }
//     else if (id < 0)
//     {
//         // fork 失败
//         perror("fork");
//         return 1;
//     }

//     // 父进程继续运行
//     while (1)
//     {
//         sleep(1);
//     }

//     return 0;
// }

// #include <stdio.h>
// #include <stdlib.h>
// #include <signal.h>
// #include <sys/types.h>
// #include <sys/wait.h>
// #include <unistd.h>

// void Count(int cnt)
// {
//     while (cnt)
//     {
//         printf("cnt: %2d\r", cnt);
//         fflush(stdout);
//         cnt--;
//         sleep(1);
//     }
//     printf("\n");
// }

// int main()
// {
//     struct sigaction sa;
//     // 初始化 sigaction 结构体
//     sa.sa_handler = SIG_IGN;
//     sigemptyset(&sa.sa_mask);
//     sa.sa_flags = 0;

//     // 使用 sigaction 设置 SIGCHLD 信号处理动作
//     if (sigaction(SIGCHLD, &sa, NULL) == -1) {
//         perror("sigaction");
//         return 1;
//     }

//     printf("我是父进程，%d，ppid：%d，正在等待子进程退出...\n", getpid(), getppid());

//     pid_t id = fork();
//     if (id == 0) {
//         // 子进程
//         printf("我是子进程，%d，ppid：%d，我要开始倒计时并退出啦\n", getpid(), getppid());
//         Count(5);
//         exit(1);
//     } else if (id < 0) {
//         // fork 失败
//         perror("fork");
//         return 1;
//     }

//     // 父进程继续运行
//     while (1) {
//         sleep(1);
//     }

//     return 0;
// }